/*
Copyright SecureKey Technologies Inc. All Rights Reserved.

SPDX-License-Identifier: Apache-2.0
*/
package ichain_sdk

import (
	"git.cloud.inspur.com/ichain/ichain-sdk-go/pkg/providers/iam"
	"github.com/pkg/errors"
)

type identityOptions struct {
	signingIdentity iam.SigningIdentity
	orgName         string
	username        string
}

type ContextOption func(s *identityOptions) error

func WithUser(username string) ContextOption {
	return func(o *identityOptions) error {
		o.username = username
		return nil
	}
}

func WithIdentity(signingIdentity iam.SigningIdentity) ContextOption {
	return func(o *identityOptions) error {
		o.signingIdentity = signingIdentity
		return nil
	}
}

func WithOrg(org string) ContextOption {
	return func(o *identityOptions) error {
		o.orgName = org
		return nil
	}
}

var ErrAnonymousIdentity = errors.New("missing credentials")

// newIdentity sdk的上下文中创建身份
// @param options
// @return iam.SigningIdentity
// @return error
func (sdk *IChainSDK) newIdentity(options ...ContextOption) (iam.SigningIdentity, error) {
	opts := identityOptions{
		orgName: sdk.provider.IdentityConfig().Client().Organization,
	}

	for _, option := range options {
		err1 := option(&opts)
		if err1 != nil {
			return nil, errors.WithMessage(err1, "error in option passed to create identity")
		}
	}

	// 必须指定一个创建的身份或者用户名
	if opts.signingIdentity == nil && opts.username == "" {
		return nil, ErrAnonymousIdentity
	}

	if opts.signingIdentity != nil {
		return opts.signingIdentity, nil
	}

	if opts.username == "" || opts.orgName == "" {
		return nil, errors.New("invalid options to create identity")
	}

	mgr, ok := sdk.provider.IdentityManager(opts.orgName)
	if !ok {
		return nil, errors.New("invalid options to create identity, invalid org name")
	}

	user, err := mgr.GetSigningIdentity(opts.username)
	if err != nil {
		return nil, err
	}

	return user, nil
}
